Kubernetes Deployment
This document describes the deployment of the SyncNow application on Kubernetes, including configuration, secrets, services, deployment, and ingress.
1. ConfigMap
syncnow-webapp-configmap
Stores web application configuration.
- webconfig:
{ "apiEndpoint": "https://syncnowapp.example.com" }
2. Secrets
-
syncnow-db-password:
Stores the database password (base64 encoded). -
redis-password:
Stores the Redis password (base64 encoded), redis is used for the AI. -
ai-settings-secret:
Stores the AI API key (base64 encoded), AI Key, we currently support Azure OpenAI
3. Service
syncnow-service
- Type:
ClusterIP
- Port:
5030
4. Deployment
syncnow
- Replicas:
1
- Image:
repo.example.com/syncnowserver:latest
- Port:
5030
- Liveness/Readiness Probes:
/v1.0/Configuration/IsServiceReady
- Volume: Mounts
webconfig
from ConfigMap to/WebApp/app.json
- Image Pull Secret:
imagepullsecret
Environment Variables
Refer to Environment Variables Configuration Parameters for all environment variables.
5. Volumes
- syncnow-webapp-volume:
Mounts thewebconfig
from the ConfigMap to/WebApp/app.json
.
6. Ingress
syncnowingress
- Host:
SyncNowApp.example.com
- TLS: Enabled (secret:
syncnowsecret
) - Service:
syncnow-service:5030
7. Affinity
- Pod anti-affinity ensures pods are distributed across nodes.
Notes
- All secrets are base64 encoded.
- Update secrets and config as needed for your environment.
- Ensure image pull secrets are configured in your cluster.
Example
apiVersion: v1
kind: ConfigMap
metadata:
name: syncnow-webapp-configmap
labels:
app: syncnow
data:
webconfig: |
{
"apiEndpoint": "https://SyncNowApp.example.com"
}
---
apiVersion: v1
kind: Secret
metadata:
name: syncnow-db-password
labels:
app: syncnow
type: Opaque
data:
password: "REPLACE_BASE64_PASSWORD"
---
apiVersion: v1
kind: Secret
metadata:
name: redis-password
labels:
app: syncnow
type: Opaque
data:
password: "REPLACE_BASE64_PASSWORD"
---
apiVersion: v1
kind: Secret
metadata:
name: ai-settings-secret
labels:
app: syncnow
type: Opaque
data:
apikey: "REPLACE_BASE64_APIKEY"
---
apiVersion: v1
kind: Service
metadata:
name: syncnow-service
labels:
app: syncnow
spec:
type: ClusterIP
ports:
- port: 5030
targetPort: 5030
selector:
app: syncnow
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: syncnow
labels:
app: syncnow
spec:
replicas: 3
selector:
matchLabels:
app: syncnow
template:
metadata:
labels:
app: syncnow
spec:
containers:
- name: syncnow
image: repo.example.com/syncnowserver:latest
resources:
limits:
memory: "1024Mi"
ports:
- containerPort: 5030
imagePullPolicy: Always
securityContext:
readOnlyRootFilesystem: false
runAsNonRoot: true
runAsUser: 999
livenessProbe:
httpGet:
path: /v1.0/Configuration/IsServiceReady
port: 5030
initialDelaySeconds: 5
periodSeconds: 10
readinessProbe:
httpGet:
path: /v1.0/Configuration/IsServiceReady
port: 5030
initialDelaySeconds: 5
periodSeconds: 10
volumeMounts:
- name: syncnow-webapp-volume
mountPath: /WebApp/app.json
subPath: webconfig
env:
- name: SETTINGS__TENANT
value: SyncNowApp
- name: SETTINGS__DATABASECONFIGURATION__DATABASETYPE
value: PostgreSQL
- name: SETTINGS__DATABASECONFIGURATION__SERVER
value: postgresql-dev1.example.com
- name: SETTINGS__DATABASECONFIGURATION__PORT
value: "5432"
- name: SETTINGS__DATABASECONFIGURATION__USERNAME
value: SyncNowUser
- name: SETTINGS__DATABASECONFIGURATION__PASSWORD
valueFrom:
secretKeyRef:
name: syncnow-db-password
key: password
- name: SETTINGS__DATABASECONFIGURATION__TRANSPORTENCRYPT
value: "False"
- name: SETTINGS__DATABASECONFIGURATION__DATABASE
value: SyncNowApp
- name: SETTINGS__CACHESTORECONFIGURATION__SERVER
value: "redis-stack.example.com"
- name: SETTINGS__CACHESTORECONFIGURATION__TIMEOUT
value: "60"
- name: SETTINGS__CACHESTORECONFIGURATION__PORT
value: "6379"
- name: SETTINGS__CACHESTORECONFIGURATION__USERNAME
value: ""
- name: SETTINGS__CACHESTORECONFIGURATION__PASSWORD
valueFrom:
secretKeyRef:
name: syncnow-db-password
key: password
- name: SETTINGS__VECTORDATABASECONFIGURATION__DATABASETYPE
value: "Redis"
- name: SETTINGS__VECTORDATABASECONFIGURATION__TIMEOUT
value: "60"
- name: SETTINGS__VECTORDATABASECONFIGURATION__SERVER
value: "redis-stack.example.com"
- name: SETTINGS__VECTORDATABASECONFIGURATION__URL
value: "redis-stack.example.com"
- name: SETTINGS__VECTORDATABASECONFIGURATION__PORT
value: "6379"
- name: SETTINGS__VECTORDATABASECONFIGURATION__USERNAME
value: ""
- name: SETTINGS__VECTORDATABASECONFIGURATION__PASSWORD
valueFrom:
secretKeyRef:
name: syncnow-db-password
key: password
- name: SETTINGS__AISETTINGS__ISAIACTIVE
value: "true"
- name: SETTINGS__AISETTINGS__CHATCOMPLETIONAIPROVIDER
value: "AzureOpenAI"
- name: SETTINGS__AISETTINGS__CHATCOMPLETIONMODELNAME
value: "gpt-4o-mini"
- name: SETTINGS__AISETTINGS__EMBEDDINGDEPLOYMENTNAME
value: "text-embedding-ada-002"
- name: SETTINGS__AISETTINGS__APIKEY
valueFrom:
secretKeyRef:
name: ai-settings-secret
key: apikey
- name: SETTINGS__AISETTINGS__PROVIDERURL
value: "https://ai-endpoint.cognitiveservices.azure.com/"
- name: ASPNETCORE_Environment
value: Development
- name: ASPNETCORE_URLS
value: http://*:5030
volumes:
- name: syncnow-webapp-volume
configMap:
name: syncnow-webapp-configmap
imagePullSecrets:
- name: imagepullsecret
affinity:
podAntiAffinity:
preferredDuringSchedulingIgnoredDuringExecution:
- weight: 100
podAffinityTerm:
labelSelector:
matchExpressions:
- key: "app"
operator: In
values:
- syncnow
topologyKey: "kubernetes.io/hostname"
---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: syncnowingress
annotations:
nginx.ingress.kubernetes.io/proxy-body-size: "600m"
spec:
ingressClassName: nginx
tls:
- hosts:
- SyncNowApp.example.com
secretName: syncnowsecret
rules:
- host: SyncNowApp.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: syncnow-service
port:
number: 5030